package com.redlion.weapon;

import java.util.ArrayList;

import org.andengine.extension.physics.box2d.PhysicsConnector;
import org.andengine.extension.physics.box2d.util.Vector2Pool;
import org.andengine.opengl.texture.region.ITiledTextureRegion;
import org.andengine.opengl.texture.region.TextureRegion;
import org.andengine.util.adt.pool.Pool;
import org.andengine.util.math.MathUtils;

import com.badlogic.gdx.math.Vector2;
import com.redlion.Game;
import com.redlion.GameActivity;
import com.redlion.UpdateTask;
import com.redlion.object.Shot;
import com.redlion.object.ShotPool;

import android.util.Log;

public class WeaponCatalog {
	public static final short WEAPON_LASER = 0;
	public static final short WEAPON_DEBUG = 1;
	public static ArrayList<WeaponEntry> weapons = new ArrayList<WeaponEntry>();
	private static ArrayList<UpdateTaskListener> listener = new ArrayList<UpdateTaskListener>();

	static {
		Upgrade u1 = new Upgrade(2, 20, 200);
		Upgrade u2 = new Upgrade(2, 40, 300);
		Upgrade u3 = new Upgrade(1, 50, 500);
		WeaponEntry ce1 = new WeaponEntry("Laser", WEAPON_LASER);
		ce1.addUpgrade(u1);
		ce1.addUpgrade(u2);
		ce1.addUpgrade(u3);
		ce1.setOnFireListener(new OnFireListener() {
			int planetOffset = 110;

			@Override
			public void firePlanetCannon(final Cannon cannon) {

				float degAngle = MathUtils.degToRad(Game.planet.sprite.getRotation() + cannon.sprite.getRotation());
				final Vector2 dir = Vector2Pool.obtain((float) Math.cos(degAngle), (float) Math.sin(degAngle)).nor();
				Vector2 start = Vector2Pool.obtain(dir).mul(planetOffset).add(Game.planet.center);
				final Vector2 temp = Vector2Pool.obtain(start).mul(1f / 32f);

				final Shot shot = Game.pools.bulletPool.obtainPoolItem();
				notifyUpdateListener(new UpdateTask() {
					@Override
					public void run() {
						shot.activate();
						shot.body.setTransform(temp.x, temp.y, 0);
						shot.shoot(dir);
					}
				});
				Vector2Pool.recycle(temp);
			}

			@Override
			public void firePlayerWeapon(PlayerWeapon playerWeapon) {
				// TODO Auto-generated method stub
				
			}
		});
		weapons.add(ce1);
		WeaponEntry ce2 = new WeaponEntry("Pulse", WEAPON_DEBUG);
		ce2.addUpgrade(u1);
		ce2.addUpgrade(u2);
		ce2.addUpgrade(u3);
		ce2.setOnFireListener(new OnFireListener() {
			int planetOffset = 110;
			int length = 1000;

			@Override
			public void firePlanetCannon(Cannon c) {
				float degAngle = MathUtils.degToRad(Game.planet.sprite.getRotation() + c.sprite.getRotation());
				c.dir = Vector2Pool.obtain((float) Math.cos(degAngle), (float) Math.sin(degAngle)).nor();
				Vector2 start = Vector2Pool.obtain(c.dir).mul(planetOffset).add(Game.planet.center);
				Vector2 end = Vector2Pool.obtain(c.dir).mul(length).add(Game.planet.center);
				final LaserStroke line = Game.pools.laserStrokePool.obtainPoolItem();
				line.setPosition(start.x, start.y, end.x, end.y);
			}

			@Override
			public void firePlayerWeapon(PlayerWeapon playerWeapon) {
				// TODO Auto-generated method stub
				
			}
		});
		weapons.add(ce2);

	}

	public static WeaponEntry getWeapon(int i) {
		for (WeaponEntry w : weapons) {
			if (w.weaponIndex == i)
				return w;
		}
		return null;
	}

	public static void bindTexture(short index, int tileIndex) {
		// Log.d("Debug", getWeapon(index).name + mWeaponRegion.getTextureX() +
		// " , " + mWeaponRegion.getTextureY());
		if (contains(index))
			getWeapon(index).mTileIndex = tileIndex;
	}

	public static void bindAnimationTexture(short weaponIndex, ITiledTextureRegion mWeaponRegion, int[] indices, int startIndex) {
		if (contains(weaponIndex))
			getWeapon(weaponIndex).mTileIndex = startIndex;
		if (contains(weaponIndex)) {
			getWeapon(weaponIndex).mTiledTextureRegion = mWeaponRegion;
			if (indices.length > 0) {
				getWeapon(weaponIndex).textureIndices = indices;
				getWeapon(weaponIndex).mTileIndex = indices[0];
			}
		}
	}

	private static void notifyUpdateListener(UpdateTask updateTask){
		for (UpdateTaskListener l : listener) {
			l.onUpdateTask(updateTask);
		}
	}
	
	private static boolean contains(int weaponIndex) {
		for (WeaponEntry w : weapons) {
			if (w.weaponIndex == weaponIndex)
				return true;
		}
		return false;
	}

	public static Upgrade getUpgrade(int weaponIndex, int upgradeIndex) {
		if (contains(weaponIndex))
			return getWeapon(weaponIndex).getUpgrade(upgradeIndex);
		return null;
	}

	public static OnFireListener getOnFireListener(int weaponIndex) {
		if (contains(weaponIndex))
			return getWeapon(weaponIndex).getFireListener();
		return null;
	}
	
	public static void registerUpdateTaskListener(UpdateTaskListener l){
		listener.add(l);
	}
	public static void removeUpdateTaskListener(UpdateTaskListener l){
		listener.remove(l);
	}
}
